﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using MiniFox.Utility;
using MiniFox.Security;
using System.Globalization;

namespace MiniFox.Infrastructure
{
    /// <summary>
    /// 票据
    /// </summary>
    public class Ticket
    {
        /// <summary>
        /// 分隔符
        /// </summary>
        protected const char SPLITER = '#';
        string _ticketId;
        DateTimeOffset _creationTime;
        int _duration;

        /// <summary>
        /// 使用指定ID，构建票据对象，票据生产时间默认为当前本地时间，过期时长默认为3600秒
        /// </summary>
        /// <param name="ticketId">票据ID</param>
        public Ticket(string ticketId) : this(ticketId, 3600)
        {

        }
        /// <summary>
        /// 使用指定ID，构建票据对象，票据生产时间默认为当前本地时间
        /// </summary>
        /// <param name="ticketId">票据ID</param>
        /// <param name="duration">过期时长(单位：秒, 默认值3600)</param>
        public Ticket(string ticketId, int duration) : this(ticketId, DateTimeOffset.Now, duration)
        {
        }
        /// <summary>
        /// 
        /// </summary>
        /// <param name="ticketId">票据ID</param>
        /// <param name="creationTime">创建时间</param>
        /// <param name="duration">过期时长(单位：秒, 默认值3600)</param>
        protected Ticket(string ticketId, DateTimeOffset creationTime, int duration)
        {
            _ticketId = ticketId;
            _creationTime = creationTime;
            _duration = duration;
        }

        /// <summary>
        /// 票据转成加密字符串
        /// </summary>
        /// <returns></returns>
        public override string ToString()
        {
            string token = this.TicketID.ToString() +
                SPLITER + this.CreationTime.ToString(GlobalStandardFormat.COMPLETE_DATETIME_OFFSET_FORMAT) +
                SPLITER + this.Duration;
            return token.DesEncrypt();
        }
        /// <summary>
        /// 获取票据ID
        /// </summary>
        public string TicketID
        {
            get { return _ticketId; }
        }
        /// <summary>
        /// 出票时间
        /// </summary>
        public DateTimeOffset CreationTime
        {
            get { return _creationTime; }
        }
        /// <summary>
        /// 票据过期时间
        /// </summary>
        public virtual DateTimeOffset ExpiredTime
        {
            get { return CreationTime.AddSeconds(this.Duration); }
        }
        /// <summary>
        /// 有效时长(秒)
        /// </summary>
        public int Duration
        {
            get { return _duration; }
        }
        /// <summary>
        /// 将指定加密字符串转换成票据
        /// </summary>
        /// <param name="ticketString"></param>
        /// <returns></returns>
        public static implicit operator Ticket(string ticketString)
        {
            if (string.IsNullOrEmpty(ticketString))
                return null;
            var str = ticketString.DesDecrypt();
            string[] datas = str.Split(SPLITER);
            string ticketId = datas[0];

            DateTimeOffset creationTime = DateTimeOffset.ParseExact(datas[1], GlobalStandardFormat.COMPLETE_DATETIME_OFFSET_FORMAT, CultureInfo.CurrentCulture.DateTimeFormat, DateTimeStyles.None);
            int duration = int.Parse(datas[2]);
            Ticket ticket = new Ticket(ticketId, creationTime, duration);
            return ticket;
        }
        /// <summary>
        /// 票据转成加密字符串
        /// </summary>
        /// <param name="ticket"></param>
        /// <returns></returns>
        public static implicit operator string(Ticket ticket)
        {
            if (ticket == null)
                return null;
            return ticket.ToString();
        }

        /// <summary>
        /// 是否已经过期
        /// </summary>
        /// <returns></returns>
        public bool IsExpired()
        {
            return DateTimeOffset.Now > this.ExpiredTime;
        }

    }
}
